package handler

import (
	"../model"
	"../utils"
	"encoding/json"
	"fmt"
	"github.com/julienschmidt/httprouter"
	"io/ioutil"
	"net/http"
	"strconv"
)

type parseModel struct {
	ID    uint64      `json:"id"`
	Limit bool        `json:"limit"`
	Name  string      `json:"name"`
	Allow model.Allow `json:"allow"`
	Image string      `json:"image"`
	Disable   bool       `json:"disable"`
}

func parseQueryData(r *http.Request) parseModel {
	result, _ := ioutil.ReadAll(r.Body)
	r.Body.Close()

	var m parseModel
	json.Unmarshal([]byte(result), &m)
	return m
}

func GetItembank(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	r.ParseForm()
	var err error
	var b []byte

	response := Response{}.Default()
	id, _ := strconv.ParseUint(ps.ByName("id"), 10, 64)
	itembank := model.Itembank{ID: id}
	response.Body["itembank"] = itembank.Get()
	b, err = json.Marshal(response)
	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func GetRelatedQuestions(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	r.ParseForm()
	var err error
	var b []byte

	response := Response{}.Default()
	id, _ := strconv.ParseUint(ps.ByName("id"), 10, 64)
	itembank := model.Itembank{ID: id}
	response.Body["questions"] = itembank.GetRelatedQuestions()
	b, err = json.Marshal(response)
	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func CreateItembank(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	userid := utils.GetUserInfoFromContext(r.Context())

	result, _ := ioutil.ReadAll(r.Body)
	r.Body.Close()

	type parseModel struct {
		ID    uint64      `json:"id"`
		Limit bool        `json:"limit"`
		Name  string      `json:"name"`
		Allow model.Allow `json:"allow"`
		Image string      `json:"image"`
	}

	var m parseModel
	json.Unmarshal([]byte(result), &m)
	bank := &model.Itembank{}
	bank.ID = m.ID
	bank.Creator = userid
	bank.Name = m.Name
	bank.Limited = m.Limit
	bank.AllowType = m.Allow.Type
	bank.Image = m.Image

	fmt.Printf("model %v \n", m)
	response := Response{}.Default()
	if err := bank.Save(m.Allow.Keys); err != nil {
		response.Code = StatusNotAcceptable
		response.Message = "Create itembank failed!"
	} else {
		response.Body["id"] = bank.ID
	}

	b, err := json.Marshal(response)

	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}


func UpdateItembank(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	userid := utils.GetUserInfoFromContext(r.Context())

	query := parseQueryData(r)
	bank := &model.Itembank{}
	bank.ID = query.ID
	bank.Creator = userid
	bank.Name = query.Name
	bank.Image = query.Image
	bank.Disable = query.Disable

	fmt.Printf("model %v \n", bank)
	response := Response{}.Default()
	if err := bank.Update(); err != nil {
		response.Code = StatusNotAcceptable
		response.Message = "Create itembank failed!"
	} else {
		response.Body["itembank"] = bank.Get()
	}

	b, err := json.Marshal(response)

	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func GetItembanks(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	var err error
	var b []byte

	response := Response{}.Default()
	response.Body["itembanks"] = model.Itembank{}.GetAll()
	b, err = json.Marshal(response)

	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func RemoveItembank(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	type parseModel struct {
		ID uint64 `json:"id"`
	}

	var m parseModel
	var err error
	var b []byte

	userid := utils.GetUserInfoFromContext(r.Context())

	result, _ := ioutil.ReadAll(r.Body)
	r.Body.Close()

	json.Unmarshal([]byte(result), &m)

	itembank := model.Itembank{}

	response := Response{}.Default()
	if itembank.IsCreator(userid, m.ID) {
		if err := itembank.Remove(m.ID); err != nil {
			response.Message = "删除成功"
		} else {
			response.Code = StatusNotAcceptable
			response.Message = "无权删除，请停止操作"
		}
	} else {
		response.Code = StatusNotAcceptable
		response.Message = "无权删除，请停止操作"
	}
	b, err = json.Marshal(response)
	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func AddRelateQuestions(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	r.ParseForm()
	type parseModel struct {
		Questions []uint64 `json:"questions"`
	}
	var m parseModel

	var err error
	var b []byte

	result, _ := ioutil.ReadAll(r.Body)
	r.Body.Close()
	json.Unmarshal([]byte(result), &m)

	response := Response{}.Default()
	id, _ := strconv.ParseUint(ps.ByName("id"), 10, 64)
	itembank := model.Itembank{ID: id}
	if err = itembank.SaveQuestions(m.Questions); err != nil {

	}
	b, err = json.Marshal(response)
	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func RemoveRelatedQuestions(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	r.ParseForm()
	type parseModel struct {
		Questions []uint64 `json:"questions"`
	}

	var m parseModel
	result, _ := ioutil.ReadAll(r.Body)
	r.Body.Close()
	json.Unmarshal([]byte(result), &m)
	id, _ := strconv.ParseUint(ps.ByName("id"), 10, 64)
	itembank := model.Itembank{ID: id}

	response := Response{}.Default()
	fmt.Printf("m %v \n", m.Questions)
	if err := itembank.DeleteQuestions(m.Questions); err != nil {

	}

	b, err := json.Marshal(response)
	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func ChangeStatus(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	type parseModel struct {
		ID uint64 `json:"id"`
		Status string  `json:"status"`
	}

	var m parseModel

	result, _ := ioutil.ReadAll(r.Body)
	r.Body.Close()

	json.Unmarshal([]byte(result), &m)

	itembank := model.Itembank{}
	response := Response{}.Default()
	if m.Status == "disable" {
		if err := itembank.SetDisable(m.ID); err != nil {
			response.Message = "禁用成功"
		} else {
			response.Code = StatusNotAcceptable
			response.Message = "无权启用，请停止操作"
		}
	} else if m.Status == "enable"{
		if err := itembank.SetEnable(m.ID); err != nil {
			response.Message = "启用成功"
		} else {
			response.Code = StatusNotAcceptable
			response.Message = "无权启用，请停止操作"
		}
	}

	b, err := json.Marshal(response)
	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func UploadItembankImage(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	var err error
	var b []byte
	fmt.Println("uploading image  ")
	imageInfo , _ := uploadImage(r)
	fmt.Printf("imageinfo %v \n", imageInfo)
	id, _ := strconv.ParseUint(ps.ByName("id"), 10, 64)
	bank := model.Itembank{ID:id, Image: imageInfo.Url}
	if err = bank.SaveImage(); err != nil {
		fmt.Print(err)
	}
	b, err = json.Marshal(imageInfo)
	if err!=nil {
		fmt.Print( err )
	}
	w.Write(b)
}

//由于 EnableItembank 和 DisableItembank大部分代码相关，所以封闭在这里
func changeStatus(w http.ResponseWriter, r *http.Request, isDisable bool) {
	type parseModel struct {
		ID uint64 `json:"id"`
	}

	var m parseModel

	userid := utils.GetUserInfoFromContext(r.Context())

	result, _ := ioutil.ReadAll(r.Body)
	r.Body.Close()

	json.Unmarshal([]byte(result), &m)

	itembank := model.Itembank{}
	response := Response{}.Default()
	if itembank.IsCreator(userid, m.ID) {
		if isDisable {
			if err := itembank.SetDisable(m.ID); err != nil {
				response.Message = "禁用成功"
			} else {
				response.Code = StatusNotAcceptable
				response.Message = "无权启用，请停止操作"
			}
		} else {
			if err := itembank.SetEnable(m.ID); err != nil {
				response.Message = "启用成功"
			} else {
				response.Code = StatusNotAcceptable
				response.Message = "无权启用，请停止操作"
			}
		}

	} else {
		response.Code = StatusNotAcceptable
		response.Message = "无权操作"
	}
	b, err := json.Marshal(response)
	if err != nil {
		fmt.Printf("errors :", err)
	}
	w.Write(b)
}

func EnableItembank(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	changeStatus(w, r, false)
}

func DisableItembank(w http.ResponseWriter, r *http.Request, ps httprouter.Params) {
	changeStatus(w, r, true)
}
